use std::fmt;
use crate::{
    config::error::ConfigError, 
    recipe::VersionError,
    backup::BackupError,
    restore::RestoreError,
};

pub type CResult<T> = Result<T,ChunkIoError>;

#[derive(Debug)]
pub enum ChunkIoError {
    Config(ConfigError),
    Version(VersionError),
    Backup(BackupError),
    Restore(RestoreError),
}

impl fmt::Display for ChunkIoError {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        match self {
            ChunkIoError::Config(e) => write!(f,"config::{}",e),
            ChunkIoError::Backup(e) => write!(f,"backup::{}",e),
            ChunkIoError::Restore(e) => write!(f,"restore::{}",e),
            ChunkIoError::Version(e) => write!(f,"version::{}",e),
        }
    }
}

impl std::error::Error for ChunkIoError {}

impl From<BackupError> for ChunkIoError {
    fn from(value: BackupError) -> Self {
        Self::Backup(value)
    }
}

impl From<RestoreError> for ChunkIoError {
    fn from(value: RestoreError) -> Self {
        Self::Restore(value)
    }
}

impl From<ConfigError> for ChunkIoError {
    fn from(value: ConfigError) -> Self {
        Self::Config(value)
    }
}

impl From<VersionError> for ChunkIoError {
    fn from(value: VersionError) -> Self {
        Self::Version(value)
    }
}